package com.autumn.mybatis.criterion;

import java.util.HashSet;
import java.util.Set;

import com.autumn.mybatis.criterion.expressions.ColumnExpression;
import com.autumn.mybatis.criterion.expressions.PropertyExpression;
import com.autumn.mybatis.criterion.impl.SpecifyQuerySectionImpl;
import com.autumn.mybatis.metadata.EntityTable;
import com.autumn.util.ExceptionUtils;

/**
 * 指定查询
 * 
 * @author 老码农
 *
 *         2017-10-30 11:33:01
 */
public class SpecifyQuery extends Query {

	/**
	 * 
	 */
	private static final long serialVersionUID = 1837850271188771492L;
	private final Set<String> selectList = new HashSet<>();

	/**
	 * 
	 * @param resultClass
	 */
	public SpecifyQuery() {
		super();
	}

	/**
	 * 
	 * @param entityClass
	 */
	public SpecifyQuery(Class<?> entityClass) {
		super(entityClass);
	}

	/**
	 * 
	 * @param entityTable
	 */
	public SpecifyQuery(EntityTable entityTable) {
		super(entityTable);

	}

	/**
	 * 选择 Select 的列
	 * 
	 * @param names
	 *            属性名或列名称
	 * @return
	 */
	public SpecifyQuery select(String... names) {
		for (String name : names) {
			add(name);
		}
		return this;
	}
	
	/**
	 * 重置
	 */
	@Override
	public void reset() {
		super.reset();		
		this.selectList.clear();
	}

	private void add(String name) {
		ColumnExpression column = this.column(name);
		String columnName = column.getColumnName();
		if (column instanceof PropertyExpression) {
			PropertyExpression property = (PropertyExpression) column;
			if (!property.getColumnName().equalsIgnoreCase(property.getColumn().getPropertyName())) {
				columnName = String.format("%s AS %s", property.getColumnName(),
						property.getColumn().getPropertyName());
			}
		}
		if (!selectList.contains(columnName)) {
			selectList.add(columnName);
		}
	}

	/**
	 * 生成
	 * 
	 * @return
	 */
	@Override
	public ISpecifyQuerySection builderSection() {
		if (this.selectList.size() == 0) {
			ExceptionUtils.throwApplicationException("至少需要一个查询属性或列。");
		}
		SpecifyQuerySectionImpl qs = new SpecifyQuerySectionImpl(this.lockMode);
		// 条件表达式
		qs.getCriterias().addAll(this.createCriteriaSections());
		setQuerySection(qs);
		qs.getSelectList().addAll(this.selectList);
		return qs;
	}

}
